package cn.matezk.lianlian.task;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.http.Header;
import cn.hutool.http.HttpRequest;
import cn.hutool.http.HttpResponse;
import cn.hutool.json.JSONArray;
import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import cn.matezk.lianlian.dao.DeviceDao;
import cn.matezk.lianlian.dao.SimRenewDao;
import cn.matezk.lianlian.dto.DeviceDto;
import cn.matezk.lianlian.dto.SimRenewDto;
import cn.matezk.lianlian.model.Device;
import cn.matezk.lianlian.model.SimRenew;
import com.xxl.job.core.context.XxlJobHelper;
import com.xxl.job.core.handler.annotation.XxlJob;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.*;

@Component
@Slf4j
public class DyFlowTask {
    @Autowired
    private DeviceDao deviceDao;
    @Autowired
    private SimRenewDao simRenewDao;

    private static final String API_TOKEN = "Bearer eyJhbGciOiJIUzUxMiJ9.eyJsb2dpbl91c2VyX2tleSI6Ijg0OTg4ZWE2LWE3MGYtNGUyOS1iMDIzLTM2OTFhNjU3ZTYzZiJ9.ILyGkLYQ9O-Hl1FVT2FaQ5lGLgEWgoDuTPwEQudPaC9ADSqxzrkcu3QG-RcPXYJC8_Xejpk-nTUh0NOb_5s4aQ";
    private static final int PAGE_SIZE = 500;

    @XxlJob("dyFlowSyncTask")
    public void execute() throws InterruptedException {
        List<String> iccids = new ArrayList<>();
        // 查询所有卡
        int pageNum = 1;
        DeviceDto deviceDto = new DeviceDto();
        deviceDto.setPageSize(PAGE_SIZE);
        deviceDto.setCardSourceList(Arrays.asList("", "DY"));
        while (true) {
            deviceDto.setPageNo(pageNum ++);
            List<Device> deviceList = deviceDao.select(deviceDto);
            for (Device device : deviceList) {
                if (ObjectUtil.isEmpty(device.getIccid()))  continue;
                iccids.add(device.getIccid());
            }
            if (ObjectUtil.isEmpty(deviceList) || deviceList.size() != PAGE_SIZE)
                break;
        }
        if (ObjectUtil.isEmpty(iccids)) return;

        List<Device> cards = new ArrayList<>();

        // 批量查询卡详情
        List<List<String>> array = CollUtil.split(iccids, 100);
        JSONObject params = JSONUtil.createObj();
        for (List<String> item : array) {
            try {
                params.set("iccidList", item);
                HttpResponse response = HttpRequest.post("https://5giot.cn/prod-api/open/iotCard/detail/batch")
                        .body(params.toString())
                        .header(Header.AUTHORIZATION, API_TOKEN)
                        .execute();
                if (!response.isOk()) continue;
                JSONObject object = JSONUtil.parseObj(response.body());
                if (object.getInt("code") != 200) {
                    log.error(response.body());
                    break;
                }
                JSONArray data = object.getJSONArray("data");
                for (int i = 0; i < data.size(); i++) {
                    JSONObject detail = data.getJSONObject(i);
                    cards.add(Device.buildCard("DY", detail.getStr("iccid"), detail.getDate("expireDate", DateUtil.parseDate("2000-01-01"))));
                }

            } finally {
                Thread.sleep(1000 * 10);
            }
        }
        if (ObjectUtil.isNotEmpty(cards)) {
            List<List<Device>> cardArray = CollUtil.split(cards, 500);
            for (List<Device> cs : cardArray) {
                deviceDao.batchUpdateCardInfo(cs);
            }
        }
    }

    @XxlJob("dyFlowRenewTask")
    public void flowRenew() throws InterruptedException {
        SimRenewDto simRenewDto = new SimRenewDto();
        simRenewDto.setCardSource("DY");
        Calendar calendar = Calendar.getInstance();
        calendar.set(Calendar.HOUR, 0);
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        calendar.set(Calendar.DATE, 1);
        calendar.add(Calendar.MONTH, 1);
        simRenewDto.setExpireDateBefore(calendar.getTime());

        List<SimRenew> renewList = simRenewDao.filter(simRenewDto);
        if (ObjectUtil.isEmpty(renewList)) return;

        List<List<SimRenew>> renewArray = CollUtil.split(renewList, 500);
        for (List<SimRenew> item : renewArray) {
            List<SimRenew> successRenew = new ArrayList<>();
            try {
                Map<String, SimRenew> renewMap = new HashMap<>();
                for (SimRenew sim : item) {
                    renewMap.put(sim.getIccid(), sim);
                }
                JSONObject params = JSONUtil.createObj()
                        .set("iccidList", renewMap.keySet());
                HttpResponse response = HttpRequest.post("https://5giot.cn/prod-api/open/iotCard/applyForRenewal")
                        .body(params.toString())
                        .header(Header.AUTHORIZATION, API_TOKEN)
                        .execute();
                if (!response.isOk()) continue;
                String body = response.body();
                XxlJobHelper.log(body);
                JSONObject object = JSONUtil.parseObj(response.body());
                if (object.getInt("code") != 200) {
                    continue;
                }
                if (!object.containsKey("data")) break;
                JSONObject data = object.getJSONObject("data");
                if (!data.containsKey("suceessIccIdList")) continue;
                JSONArray successList = data.getJSONArray("suceessIccIdList");
                if (successList.size() == 0) continue;
                String payno = data.getStr("transactionNo");
                for (int i = 0; i < successList.size(); i ++) {
                    SimRenew simRenew = renewMap.get(successList.getStr(i));
                    calendar.setTime(simRenew.getIccidExpireDate());
                    calendar.add(Calendar.MONTH, 12);
                    simRenew.setIccidExpireDate(calendar.getTime());
                    simRenew.setPayno(payno);
                    simRenew.setMonths(12);
                    successRenew.add(simRenew);
                }
            } catch (Exception e) {
                XxlJobHelper.log(e);
            } finally {
                if (ObjectUtil.isNotEmpty(successRenew)) {
                    simRenewDao.insertBatch(successRenew);
                }
                Thread.sleep(1000 * 10);
            }
        }
    }
}
